package com.tuanzi.loan.business.repository.receipt.product.impl;

import com.tuanzi.loan.business.entity.receipt.product.ReceiptProductPrice;
import com.tuanzi.loan.business.repository.receipt.product.custom.ReceiptProductPriceRespositoryCustom;
import com.tuanzi.loan.core.repository.JOOQBaseRepository;
import com.tuanzi.loan.vo.request.receipt.product.ReceiptProductPriceSearchRequest;
import com.tuanzi.loan.vo.response.receipt.product.ReceiptProductPriceSearchResponse;
import org.jooq.Record;
import org.jooq.RecordMapper;
import org.jooq.impl.TableImpl;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Repository;

import java.util.List;

import static com.tuanzi.loan.generated.jooq.loan.tables.LoanReceiptProductPrice.LOAN_RECEIPT_PRODUCT_PRICE;

@Repository
public class ReceiptProductPriceRespositoryImpl extends JOOQBaseRepository implements ReceiptProductPriceRespositoryCustom {
    @Override
    protected TableImpl getTable() {
        return LOAN_RECEIPT_PRODUCT_PRICE;
    }

    @Override
    public List<ReceiptProductPrice> findPriceByApplyRangeCoincide(ReceiptProductPriceSearchResponse productPrice) {
        Integer minApply = productPrice.getMinApply();
        Integer maxApply = productPrice.getMaxApply();
        return dslContext.select().from(LOAN_RECEIPT_PRODUCT_PRICE)
                //不和当前要更新的这条记录进行比较
                .where(LOAN_RECEIPT_PRODUCT_PRICE.ID.ne(productPrice.getId()))
                //和同一个产品下的区间进行比较
                .and(LOAN_RECEIPT_PRODUCT_PRICE.PRODUCT_ID.eq(productPrice.getProductId()))
                //判断当前输入的区间是否被已有的区间所包含
                .and(LOAN_RECEIPT_PRODUCT_PRICE.MIN_APPLY.between(minApply, maxApply).or(LOAN_RECEIPT_PRODUCT_PRICE.MAX_APPLY.between(minApply, maxApply)))
                .orderBy(LOAN_RECEIPT_PRODUCT_PRICE.MIN_APPLY.asc())
                .fetchInto(ReceiptProductPrice.class);
    }

    @Override
    public List<ReceiptProductPriceSearchResponse> findAllVoByCondition(ReceiptProductPriceSearchRequest searchCondition) {
        eq(LOAN_RECEIPT_PRODUCT_PRICE.PRODUCT_ID, searchCondition.getProductId());
        orderBy(LOAN_RECEIPT_PRODUCT_PRICE.MIN_APPLY, Sort.Direction.ASC);
        orderBy(LOAN_RECEIPT_PRODUCT_PRICE.CREATE_TIME, Sort.Direction.DESC);
        return search(new ReceiptProductPriceSearchResponseMapper());
    }

    @Override
    public List<ReceiptProductPrice> findAllPoByCondition(ReceiptProductPriceSearchRequest searchCondition) {
        eq(LOAN_RECEIPT_PRODUCT_PRICE.PRODUCT_ID, searchCondition.getProductId());
        orderBy(LOAN_RECEIPT_PRODUCT_PRICE.MIN_APPLY, Sort.Direction.ASC);
        orderBy(LOAN_RECEIPT_PRODUCT_PRICE.CREATE_TIME, Sort.Direction.DESC);
        return search(new ReceiptProductPriceMapper());
    }

    private final class ReceiptProductPriceSearchResponseMapper implements RecordMapper<Record, ReceiptProductPriceSearchResponse> {
        @Override
        public ReceiptProductPriceSearchResponse map(Record record) {
            ReceiptProductPriceSearchResponse response = new ReceiptProductPriceSearchResponse();
            response.setId(record.get(LOAN_RECEIPT_PRODUCT_PRICE.ID));
            response.setProductId(record.get(LOAN_RECEIPT_PRODUCT_PRICE.PRODUCT_ID));
            response.setUnitPrice(record.get(LOAN_RECEIPT_PRODUCT_PRICE.UNIT_PRICE));
            response.setMinApply(record.get(LOAN_RECEIPT_PRODUCT_PRICE.MIN_APPLY));
            response.setMaxApply(record.get(LOAN_RECEIPT_PRODUCT_PRICE.MAX_APPLY));
            response.setCreator(record.get(LOAN_RECEIPT_PRODUCT_PRICE.CREATOR));
            response.setCreateTime(record.get(LOAN_RECEIPT_PRODUCT_PRICE.CREATE_TIME));
            response.setUpdator(record.get(LOAN_RECEIPT_PRODUCT_PRICE.UPDATOR));
            response.setUpdateTime(record.get(LOAN_RECEIPT_PRODUCT_PRICE.UPDATE_TIME));
            response.setRemark(record.get(LOAN_RECEIPT_PRODUCT_PRICE.REMARK));
            response.setVersion(record.get(LOAN_RECEIPT_PRODUCT_PRICE.VERSION));
            return response;
        }
    }

    private final class ReceiptProductPriceMapper implements RecordMapper<Record,ReceiptProductPrice>{
        @Override
        public ReceiptProductPrice map(Record record) {
            ReceiptProductPrice price = new ReceiptProductPrice();
            price.setId(record.get(LOAN_RECEIPT_PRODUCT_PRICE.ID));
            price.setProductId(record.get(LOAN_RECEIPT_PRODUCT_PRICE.PRODUCT_ID));
            price.setUnitPrice(record.get(LOAN_RECEIPT_PRODUCT_PRICE.UNIT_PRICE));
            price.setMinApply(record.get(LOAN_RECEIPT_PRODUCT_PRICE.MIN_APPLY));
            price.setMaxApply(record.get(LOAN_RECEIPT_PRODUCT_PRICE.MAX_APPLY));
            price.setCreator(record.get(LOAN_RECEIPT_PRODUCT_PRICE.CREATOR));
            price.setCreateTime(record.get(LOAN_RECEIPT_PRODUCT_PRICE.CREATE_TIME));
            price.setUpdator(record.get(LOAN_RECEIPT_PRODUCT_PRICE.UPDATOR));
            price.setUpdateTime(record.get(LOAN_RECEIPT_PRODUCT_PRICE.UPDATE_TIME));
            price.setRemark(record.get(LOAN_RECEIPT_PRODUCT_PRICE.REMARK));
            price.setVersion(record.get(LOAN_RECEIPT_PRODUCT_PRICE.VERSION));
            return price;
        }
    }

}
